package edu.asu.cse360.model;

import java.beans.PropertyChangeListener;
import java.beans.PropertyChangeSupport;
import java.io.Serializable;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.JoinTable;
import javax.persistence.ManyToOne;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
import javax.persistence.OneToMany;
import javax.persistence.OneToOne;
import javax.persistence.Transient;
import org.hibernate.annotations.Type;

@NamedQueries({
    @NamedQuery(name=MenuItem.FIND_AVAILABLE_BY_RESTAURANT, query="select mi from MenuItem mi where mi.restaurant = :restaurant and mi.available = true")
})
@Entity
@javax.persistence.Table(name="menu_item")
public class MenuItem implements Serializable, Idenfiable{

    public static final String FIND_AVAILABLE_BY_RESTAURANT = "MenuItem.findAvailableByRestaurant";
    public static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    @Column(name="menu_item_id")
    private Integer id;

    @Column
    private String name;

    @Column
    private String description;

    @Column
    private Double rating;

    @Column
    private double ratingFrequency;

    @Column
    private Double price;

    @Column(name="display_order")
    private int displayOrder;

    @OneToMany(fetch=FetchType.EAGER)
    @JoinTable(
	        name="menu_item_tag",
	        joinColumns=@JoinColumn(name="menu_item_id"),
	        inverseJoinColumns=@JoinColumn(name="tag_id"))
    private Set<Tag> tags;


    @OneToMany(fetch=FetchType.EAGER)
    @JoinTable(
	        name="menu_item_ingredient",
	        joinColumns=@JoinColumn(name="menu_item_id"),
	        inverseJoinColumns=@JoinColumn(name="ingredient_id"))
    private Set<Ingredient> ingredients;

    @Column
    @Type(type="yes_no")
    private boolean available;

    @OneToOne(cascade=CascadeType.ALL)
    @JoinColumn(name="photo_id")
    private Photo photo;

    @ManyToOne
    @JoinColumn(name="restaurant_id")
    private Restaurant restaurant;

    @Column(name="time_to_cook")
    private String timeToCook;

    /**
     * @return the id
     */
    public Integer getId() {
        return id;
    }

    /**
     * @param id the id to set
     */
    public void setId(Integer id) {
        this.id = id;
    }

    /**
     * @return the name
     */
    public String getName() {
        return name;
    }

    /**
     * @param name the name to set
     */
    public void setName(String name) {
        String oldName = this.name;
        this.name = name;
    }

    /**
     * @return the description
     */
    public String getDescription() {
        return description;
    }

    /**
     * @param description the description to set
     */
    public void setDescription(String description) {
        this.description = description;
    }

    /**
     * @return the rating
     */
    public Double getRating() {
        return rating;
    }

    /**
     * @param rating the rating to set
     */
    public void setRating(Double rating) {
        this.rating = rating;
    }

    /**
     * @return the displayOrder
     */
    public int getDisplayOrder() {
        return displayOrder;
    }

    /**
     * @param displayOrder the displayOrder to set
     */
    public void setDisplayOrder(int displayOrder) {
        this.displayOrder = displayOrder;
    }

    /**
     * @return the tags
     */
    public Set<Tag> getTags() {
        return tags;
    }

    /**
     * @param tags the tags to set
     */
    public void setTags(Set<Tag> tags) {
        this.tags = tags;
    }

    /**
     * @return the ingredients
     */
    public Set<Ingredient> getIngredients() {
        return ingredients;
    }

    /**
     * @param ingredients the ingredients to set
     */
    public void setIngredients(Set<Ingredient> ingredients) {
        this.ingredients = ingredients;
    }

    /**
     * @return the available
     */
    public boolean isAvailable() {
        return available;
    }

    /**
     * @param available the available to set
     */
    public void setAvailable(boolean available) {
        this.available = available;
    }

    /**
     * @return the photo
     */
    public Photo getPhoto() {
        return photo;
    }

    /**
     * @param photo the photo to set
     */
    public void setPhoto(Photo photo) {
        this.photo = photo;
    }

    /**
     * @return the price
     */
    public Double getPrice() {
        return price;
    }

    /**
     * @param price the price to set
     */
    public void setPrice(Double price) {
        this.price = price;
    }

    /**
     * @return the restaurant
     */
    public Restaurant getRestaurant() {
        return restaurant;
    }

    /**
     * @param restaurant the restaurant to set
     */
    public void setRestaurant(Restaurant restaurant) {
        this.restaurant = restaurant;
    }

    /**
     * @return the ratingFrequency
     */
    public double getRatingFrequency() {
        return ratingFrequency;
    }

    /**
     * @param ratingFrequency the ratingFrequency to set
     */
    public void setRatingFrequency(double ratingFrequency) {
        this.ratingFrequency = ratingFrequency;
    }

    /**
     * @return the timeToCook
     */
    public String getTimeToCook() {
        return timeToCook;
    }

    /**
     * @param timeToCook the timeToCook to set
     */
    public void setTimeToCook(String timeToCook) {
        this.timeToCook = timeToCook;
    }


}
